#!/usr/bin/env python
# encoding: utf-8


from PyQt5.QtCore import *
from pyqtgraph import GraphicsLayoutWidget
import pyqtgraph as pg
import numpy as np

class GraphWindow(GraphicsLayoutWidget):
    def __init__(self):
        super(GraphWindow, self).__init__()

        self.label = pg.LabelItem(justify='right')
        self.addItem(self.label,0,1,colspan=2)
        self.plot = self.addPlot(1,1,colspan=2)
        self.curve_x = self.plot.plot([-300,0,300],[0,0,0], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")
        self.plot.setAutoVisible(y=True)
        self.plot.setYRange(-100,700)
        self.plot.setXRange(-400,400)
        self.plot.showGrid(x=True,y=True,alpha=0.5)

        # 实施移动位置
        self.scatter_pos = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 255, 5, 180))
        self.scatter_pos.setData([0],[0])
        self.plot.addItem(self.scatter_pos)

        self.curvePoint_pos = pg.CurvePoint(self.scatter_pos)
        self.plot.addItem(self.curvePoint_pos)

        self.arrow_pos = pg.ArrowItem(angle=90)
        self.arrow_pos.setParentItem(self.curvePoint_pos)
        self.text_pos = pg.TextItem("位置: x=0", anchor=(0.5, -1.0))
        self.text_pos.setParentItem(self.curvePoint_pos)

        #
        self.radioAngleShow()

        self.radioAngleUpdate(0,0,0)

        #  self.arrow_left = pg.ArrowItem(angle=90)
        #  self.arrow_left.setParentItem(self.curvePoint_pos)
        #  self.text_pos = pg.TextItem("位置: x=0", anchor=(0.5, -1.0))
        #  self.text_pos.setParentItem(self.curvePoint_pos)

        #  # 最大剂量位置
        #  self.scatter_max = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        #  self.scatter_max.setData([0],[0])
        #  self.plot.addItem(self.scatter_max)

        #  self.curvePoint_max = pg.CurvePoint(self.scatter_max)
        #  self.plot.addItem(self.curvePoint_max)

        #  # self.arrow_max = pg.ArrowItem(angle=-90)
        #  self.arrow_max = pg.ArrowItem(angle=-90, tipAngle=30, baseAngle=20, headLen=20, tailLen=100, tailWidth=2, pen=None, brush='y')
        #  self.arrow_max.setParentItem(self.curvePoint_max)
        #  html='''<div style="text-align: center">
                #  <span style="color: white;">%.1fmm</span><br>
                #  '''%(0)
        #  self.text_max = pg.TextItem(html=html, anchor=(0.5, 3.5),angle=0)
        #  self.text_max.setParentItem(self.curvePoint_max)
        #  self.curve_max = self.plot.plot([0,0],[0,600], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")
        #  self.axis_max_x = [0,0]
        #  self.axis_max_y = [0,600]

    def radioAngleShow(self):
        '''辐射角显示'''
        # 左侧50%剂量位置
        self.scatter_left = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_left.setData([-200],[0])
        self.plot.addItem(self.scatter_left)
        self.curvePoint_left = pg.CurvePoint(self.scatter_left)
        self.plot.addItem(self.curvePoint_left)
        self.arrow_left = pg.ArrowItem(angle=-90, brush='y')
        self.arrow_left.setParentItem(self.curvePoint_left)
        html=''' <span style="color: white;">%.1f</span><br> '''%(-200)
        self.text_left = pg.TextItem(html=html, anchor=(0.5, 1.5),angle=0)
        self.text_left.setParentItem(self.curvePoint_left)
        self.curve_left = self.plot.plot([-200,0],[0,600], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")

        # 右侧50%剂量位置
        self.scatter_right = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_right.setData([200],[0])
        self.plot.addItem(self.scatter_right)
        self.curvePoint_right = pg.CurvePoint(self.scatter_right)
        self.plot.addItem(self.curvePoint_right)

        self.arrow_right = pg.ArrowItem(angle=-90, brush='y')
        self.arrow_right.setParentItem(self.curvePoint_right)
        html=''' <span style="color: white;">%.1f</span><br> '''%(200)
        self.text_right = pg.TextItem(html=html, anchor=(0.5, 1.5),angle=0)
        self.text_right.setParentItem(self.curvePoint_right)
        self.curve_right = self.plot.plot([200,0],[0,600], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")

        # 最大剂量位置
        self.scatter_max = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_max.setData([0],[0])
        self.plot.addItem(self.scatter_max)
        self.curvePoint_max = pg.CurvePoint(self.scatter_max)
        self.plot.addItem(self.curvePoint_max)
        self.arrow_max = pg.ArrowItem(angle=-90, brush='y')
        self.arrow_max.setParentItem(self.curvePoint_max)
        html=''' <span style="color: white;">%.1f</span><br> '''%(0)
        self.text_max = pg.TextItem(html=html, anchor=(0.5, 1.5),angle=0)
        self.text_max.setParentItem(self.curvePoint_max)

        # 光机原点
        self.scatter_light = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_light.setData([0],[600])
        self.plot.addItem(self.scatter_light)
        self.curvePoint_light = pg.CurvePoint(self.scatter_light)
        self.plot.addItem(self.curvePoint_light)
        self.arrow_light = pg.ArrowItem(angle=-90, brush='y')
        self.arrow_light.setParentItem(self.curvePoint_light)
        html='<span style="color: yellow;">辐射源:(0,600)</span>"'
        self.text_light = pg.TextItem(html=html, anchor=(0.5, 1.5),angle=0)
        self.text_light.setParentItem(self.curvePoint_light)
        self.curve_light = self.plot.plot([0,0],[0,600], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")

    def radioAngleUpdate(self, left_pos, max_pos, right_pos):
        distance = 600
        self.scatter_left.setData([left_pos],[0])
        self.curvePoint_left.setPos(left_pos)
        html='<span style="color: yellow;">%0.1f</span>"' % left_pos
        self.text_left.setHtml(html)
        self.curve_left.setData(np.array([[left_pos,0], [max_pos, distance]]))

        self.scatter_right.setData([right_pos],[0])
        self.curvePoint_right.setPos(right_pos)
        html='<span style="color: yellow;">%0.1f</span>"' % right_pos
        self.text_right.setHtml(html)
        self.curve_right.setData(np.array([[right_pos,0], [max_pos, distance]]))

        # 最大值
        self.scatter_max.setData([max_pos],[0])
        self.curvePoint_max.setPos(max_pos)
        html='<span style="color: yellow;">%0.1f</span>"' % max_pos
        self.text_max.setHtml(html)
        self.curve_light.setData(np.array([[max_pos,0], [max_pos,distance]]))
        # 辐射源
        self.scatter_light.setData([max_pos],[distance])
        self.curvePoint_light.setPos(max_pos)
        html='<span style="color: yellow;">辐射源:(%.1f,%.1f)</span>"'%(max_pos, distance)
        self.text_light.setHtml(html)

    def updatePosScatter(self,x):
        self.scatter_pos.setData([x],[0])
        self.curvePoint_pos.setPos(float(x))
        self.text_pos.setText('[%0.1f, %0.1f]' % (x, 0))

    def addLeftRightScatter(self):
        '''辐射角显示'''
        # 左侧50%剂量位置
        self.scatter_left = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_left.setData([-200],[0])
        self.plot.addItem(self.scatter_left)

        self.curvePoint_left = pg.CurvePoint(self.scatter_left)
        self.plot.addItem(self.curvePoint_left)

        self.arrow_left = pg.ArrowItem(angle=-90, tipAngle=30, baseAngle=20, headLen=20, tailLen=40, tailWidth=2, pen=None, brush='y')
        self.arrow_left.setParentItem(self.curvePoint_left)
        html='''<div style="text-align: center">
                <span style="color: white;">%.1fmm</span><br>
                '''%(-200)
        self.text_left = pg.TextItem(html=html, anchor=(1.0, 1.5),angle=0)
        self.text_left.setParentItem(self.curvePoint_left)
        self.curve_left = self.plot.plot([-200,0],[0,600], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")
        self.axis_left_x = [-200,0]
        self.axis_left_y = [0,600]

        # 右侧50%剂量位置
        self.scatter_right = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_right.setData([200],[0])
        self.plot.addItem(self.scatter_right)

        self.curvePoint_right = pg.CurvePoint(self.scatter_right)
        self.plot.addItem(self.curvePoint_right)

        # self.arrow_right = pg.ArrowItem(angle=-90)
        self.arrow_right = pg.ArrowItem(angle=-90, tipAngle=30, baseAngle=20, headLen=20, tailLen=40, tailWidth=2, pen=None, brush='y')
        self.arrow_right.setParentItem(self.curvePoint_right)
        html='''<div style="text-align: center">
                <span style="color: white;">%.1fmm</span><br>
                '''%(200)
        # html='<div style="text-align: center"><span style="color: yellow;">(%.1f,%.1f%%)</span>"'%(200,0)
        self.text_right = pg.TextItem(html=html, anchor=(-0.0, 1.5),angle=0)
        self.text_right.setParentItem(self.curvePoint_right)
        self.curve_right = self.plot.plot([200,0],[0,600], pen=(0,200,200), symbolBrush=(0,0,200), symbolPen='w', symbol='o', symbolSize=8, name="symbol='o'")
        self.axis_right_x = [200,0]
        self.axis_right_y = [0,600]

        # 光机原点
        self.scatter_light = pg.ScatterPlotItem(size=12, pen=pg.mkPen(None), brush=pg.mkBrush(255, 5, 5, 180))
        self.scatter_light.setData([0],[600])
        self.plot.addItem(self.scatter_light)

        self.curvePoint_light = pg.CurvePoint(self.scatter_light)
        self.plot.addItem(self.curvePoint_light)

        # self.arrow_light = pg.ArrowItem(angle=-90)
        self.arrow_light = pg.ArrowItem(angle=-45, tipAngle=30, baseAngle=20, headLen=20, tailLen=40, tailWidth=2, pen=None, brush='y')
        self.arrow_light.setParentItem(self.curvePoint_light)
        html='<div style="text-align: center"><span style="color: yellow;">光源位置:(%.1f,%.1f)</span>"'%(0,600)
        self.text_light = pg.TextItem(html=html, anchor=(-0.2, 1.5),angle=0)
        self.text_light.setParentItem(self.curvePoint_light)

    def updateMaxScatter(self,x,dos,rate):
        '''更新最大剂量值位置'''
        self.scatter_max.setData([x],[0])
        self.curvePoint_max.setPos(float(x))
        html='''<div style="text-align: center">
                <span style="color: white;">%.1fmm</span><br>
                '''%(x)
        self.text_max.setHtml(html)

        self.axis_right_x[1] = x
        self.curve_right.setData(self.axis_right_x,self.axis_right_y)
        self.axis_left_x[1] = x
        self.curve_left.setData(self.axis_left_x,self.axis_left_y)
        self.axis_max_x = [x,x]
        self.curve_max.setData(self.axis_max_x,self.axis_max_y)

    def updateLeftScatter(self,x,dos,rate,angle):
        '''左侧50%剂量值位置'''
        self.scatter_left.setData([x],[0])
        self.curvePoint_left.setPos(float(x))
        html='''<div style="text-align: center">
                <span style="color: white;">%.1fmm</span><br>
                '''%(x)
        self.text_left.setHtml(html)
        self.axis_left_x[0] = x
        self.curve_left.setData(self.axis_left_x,self.axis_left_y)
        html='<div style="text-align: center"><span style="color: green;">%.1f°</span>'%angle
        self.text_angle_left.setHtml(html)

    def updateRightScatter(self,x,dos,rate,angle):
        '''右侧50%剂量值位置'''
        self.scatter_right.setData([x],[0])
        self.curvePoint_right.setPos(float(x))
        html='''<div style="text-align: center">
                <span style="color: white;">%.1fmm</span><br>
                <span style="color: red;">%.1fuGy</span><br>
                <span style="color: blue;">%.1f%%</span>
                '''%(x,dos,rate)
        self.text_right.setHtml(html)
        self.axis_right_x[0] = x
        self.curve_right.setData(self.axis_right_x,self.axis_right_y)
        html='<div style="text-align: center"><span style="color: green;">%.1f°</span>'%angle
        self.text_angle_right.setHtml(html)

    def updateRange(self,x):
        '''更新坐标移动范围'''
        pass

class RadioLineGraphWidget(GraphicsLayoutWidget):
    def __init__(self):
        super(RadioLineGraphWidget, self).__init__()
        # 右上角显示
        self.label = pg.LabelItem(justify='right')
        self.addItem(self.label, 0, 1, 1, 1)
        self.pg = pg

        # 曲线添加
        self.plot = self.pg.PlotItem()
        self.plot = self.addPlot(1, 1, colspan=2)
        self.plot.setYRange(0, 100)
        # 点位显示
        self.scatter_pos = pg.ScatterPlotItem(size=10, pen=pg.mkPen(None), brush=pg.mkBrush(255, 255, 255, 120))
        self.scatter_pos.setData([0,0],[0,1])
        self.plot.addItem(self.scatter_pos)

        self.data = np.random.normal(size=10)
        self.curve_master_data = [100, 100]
        self.curve_slave_data = [0, 0]
        self.curve_data_x = [-300, 300]
        # 曲线设置
        self.plot.setAutoVisible(y=True)
        self.plot.setTitle('通道数据实时曲线图')
        self.plot.setLabel('left', "相对剂量(%)", units='')
        self.plot.setLabel('bottom', "距离(mm)", units='')
        self.plot.addLegend()
        # 主测通道和监测通道
        self.curve_master = self.plot.plot(self.curve_data_x, self.curve_master_data, name='主测通道',
                                           pen=self.pg.mkPen('r', width=2))
        self.curve_slave = self.plot.plot(self.curve_data_x, self.curve_slave_data, name='监测通道',
                                          pen=self.pg.mkPen('g', width=2))
        # 网格显示
        self.plot.showGrid(x=True, y=True, alpha=0.7)
        # 鼠标十字移动
        self.vLine = self.pg.InfiniteLine(pen=self.pg.mkPen('b', width=1), angle=90, movable=False)
        self.hLine = self.pg.InfiniteLine(pen=self.pg.mkPen('b', width=1), angle=0, movable=False)
        self.plot.addItem(self.vLine, ignoreBounds=True)
        self.plot.addItem(self.hLine, ignoreBounds=True)
        # 鼠标移动绑定
        self.vb = self.plot.vb
        self.proxy = self.pg.SignalProxy(self.plot.scene().sigMouseMoved, rateLimit=60, slot=self.mouseMoved)
        self.plot.autoRange()

    def find_nearest(self, array, value):
        idx = (np.abs(array - value)).argmin()
        return idx

    def mouseMoved(self, evt):
        tx = np.array(self.curve_data_x)
        pos = evt[0]
        if self.plot.sceneBoundingRect().contains(pos):
            mousePoint = self.vb.mapSceneToView(pos)
            x = mousePoint.x()
            y = mousePoint.y()
            self.vLine.setPos(mousePoint.x())
            self.hLine.setPos(mousePoint.y())
            self.setCursor(Qt.BlankCursor)

            self.scatter_pos.setData([0,0],[0,1])

            idx = self.find_nearest(np.array(self.curve_data_x), x)
            pos_x = self.curve_data_x[idx]
            pos_y1 = self.curve_master_data[idx]
            pos_y2 = self.curve_slave_data[idx]

            self.scatter_pos.setData([pos_x,pos_x],[pos_y1,pos_y2])

            self.label.setText("x:%.3f,T1:%.3f,T2:%.3f" % (pos_x, pos_y1, pos_y2))

            self.label.setText("""
                                <span style='font-size: 12pt'>x=%0.3f,
                                <span style='color: green'>T1=%0.3f</span>
                                <span style='color: red'>T2=%0.3f</span>
                               """ % (pos_x, pos_y1, pos_y2))
    def drawLine(self, x, y):
        self.curve_master.setData(x=self.curve_data_x, y=self.curve_master_data)
        self.curve_slave.setData(x=self.curve_data_x, y=self.curve_slave_data)

    def draw_two(self, x, master, slave):
        if master and slave:
            self.curve_master_data = master
            self.curve_slave_data = slave
            self.curve_data_x = x

            self.curve_master.setData(x=x, y=master)
            self.curve_slave.setData(x=x, y=slave)
        else:
            self.curve_master.setData(x=[], y=[])
            self.curve_slave.setData(x=[], y=[])
        self.plot.autoRange()

    def clear_data(self):
        self.curve_data_x = []
        self.curve_master_data = []
        self.curve_slave_data = []
        self.curve_master.setData(x=self.curve_data_x, y=self.curve_master_data)
        self.curve_slave.setData(x=self.curve_data_x, y=self.curve_slave_data)

    def drawLineAppend(self):
        self.curve_master.setData(self.curve_master_data)
        self.curve_slave.setData(self.curve_slave_data)

    def tunnelZero(self):
        self.curve_data_x = []
        self.curve_slave_data = []
        self.curve_master_data = []
        self.drawLine()

